/** 
 * 每步的得分
 * 1.落到自己包过的格子中, 就是坏步 -1
 * 2.落子后会立刻被包围死, 是坏步   -被包围数
 */

function isAvalablePos(posX,posY,totalLength)
{
  if(totalLength<=posX || posX<0)
  {
    return false;
  }
  if(totalLength<=posY || posY<0)
  {
    return false;
  }
  return true;
}

/**
 * 取当前格子的上下左右被包围情况
 * return number 被包围数
 */
function surrounded(board_state,move_pos_x,move_pos_y,ns)
{
  var resultNumber = 0;
  const length = board_state.length;
  // move_pos_x+1,move_pos_y
  var funScore = (x,y)=>{
    if(!isAvalablePos(x,y, length))
    {
      resultNumber-=1;
      // ns.tprint("顶到边上-1","\t(",x,",",y,")");
    }
    else
    {
      var targetState = board_state[x][y];
      if('O'==targetState)
      {
        resultNumber-=1;
        // ns.tprint("被对方包-1");
      }
      if('#'==targetState)
      {
        resultNumber-=1;
        // ns.tprint("被坏格子包-1");
      }
    }
  };
  funScore(move_pos_x+1,move_pos_y);
  funScore(move_pos_x-1,move_pos_y);
  funScore(move_pos_x,move_pos_y+1);
  funScore(move_pos_x,move_pos_y-1);
  // if(!isAvalablePos(move_pos_x+1,move_pos_y, length))
  // {
  //   resultNumber-=1;
  // }
  // else
  // {
  //   var targetState = board_state[move_pos_x+1][move_pos_y];
  //   if('O'==targetState)
  //   {
  //     resultNumber-=1;
  //   }
  // }
  return resultNumber;
}

/**
 * 包围对手
 * 1. 证实对方的期子是相对孤立的, 至少不会被反包
 */
function surrounded_opponent(board_state,move_pos_x,move_pos_y,ns)
{
  var resultNumber = 0;
  const length = board_state.length;
  // move_pos_x+1,move_pos_y
  var fun_score = (x,y)=>{
    if(!isAvalablePos(x,y, length))
    {
    }
    else
    {
      var targetState = board_state[x][y];
      if('O'==targetState)
      {
        resultNumber+=1;
      }
    }
  };
  fun_score(move_pos_x+1,move_pos_y);
  fun_score(move_pos_x-1,move_pos_y);
  fun_score(move_pos_x,move_pos_y+1);
  fun_score(move_pos_x,move_pos_y-1);
  if(1==resultNumber)
  {
    // ns.tprint("开始计算包对方");
    resultNumber = 0;
    fun_score(move_pos_x+1,move_pos_y+1);
    fun_score(move_pos_x-1,move_pos_y-1);
    fun_score(move_pos_x-1,move_pos_y+1);
    fun_score(move_pos_x+1,move_pos_y-1);
    if(0==resultNumber)
    {
      return 1;
    }
  }


  return 0;
}

/**
 * 能构成链的
 */
function score_make_chain(board_state,move_pos_x,move_pos_y, ns)
{
  var oblique_way=0;
  var score1=0;
  var length=board_state.length;
  var fun_score = (x,y)=>{
    if(!isAvalablePos(x,y, length))
    {
      // ns.tprint("越界 ",x,",",y);
    }
    else
    {
      var targetState = board_state[x][y];
      if('X'==targetState)
      {
        score1+=1;
        // ns.tprint("130 有相临的我方");
      }
      else
      {
        // ns.tprint("\t 相临:",targetState);
      }
    }
  };

  fun_score(move_pos_x+1,move_pos_y+1);
  fun_score(move_pos_x-1,move_pos_y-1);
  fun_score(move_pos_x-1,move_pos_y+1);
  fun_score(move_pos_x+1,move_pos_y-1);  
  if(score1)
  {
    oblique_way=1;
  }
  score1 = 0;
  fun_score(move_pos_x+1,move_pos_y);
  fun_score(move_pos_x-1,move_pos_y);
  fun_score(move_pos_x,move_pos_y+1);
  fun_score(move_pos_x,move_pos_y-1);
  var horizon_and_vertical=0;
  if(score1)
  {
    horizon_and_vertical = 1;
  }
  // 只有斜的,就扩张比较快
  if(horizon_and_vertical||oblique_way)
  {
    if(oblique_way && (!horizon_and_vertical))
    {
      return 2;
    }
    else
    {
      return 1;
    }
  }
  else
  {
    return 0;
  }
}

/**
 * 落到我方已包围的空间扣分
 * 落到敌方已包围的空间加分
 */
function score_inspace_surrounded(board_state,chains,move_pos_x,move_pos_y,ns)
{
  var point_info = chains[move_pos_x][move_pos_y];
  // 零也是个链路, 并没有公共区域之分
  // if(0 == point_info)
  // {
  //   return 0;// 不在已生成的链, 还在公共区中
  // }
  // else
  {
    var length = board_state.length;
    // 十字检测:是否有相邻的棋子
    var fun_cross_detect = (x,y,board_state,char_who)=>{
      var score1 = 0;
      var fun_score = (x,y)=>{
        if(!isAvalablePos(x,y, length))
        {
          // ns.tprint("越界 196 ",x,",",y);
        }
        else
        {
          var targetState = board_state[x][y];
          if(char_who==targetState)
          {
            score1+=1;
            // ns.tprint("130 有相临的我方");
          }
          else
          {
            // ns.tprint("\t 相临:",targetState);
          }
        }
      };
      fun_score(x+1,y);
      fun_score(x-1,y);
      fun_score(x,y+1);
      fun_score(x,y-1);
      if(score1)return true;
      return false;
    };

    // 1. 取得这个链路的所有格子:
    // 以[x,y]为单元
    var points_of_this_chain = [];
    for(var x=0;x<board_state.length;++x)
    {
      for(var y=0;y<length;++y)
      {
        if(chains[x][y] == point_info)
        {
          points_of_this_chain.push([x,y]);

        }
      }
    }// END for

    var has_us = false;
    var has_opponent = false;
    for(var i=0;i<points_of_this_chain.length;++i)
    {
      var x = points_of_this_chain[i][0];
      var y = points_of_this_chain[i][1];
      var result1 = fun_cross_detect(x,y,board_state,'X');
      if(result1) has_us = true;
      var result2 = fun_cross_detect(x,y,board_state,'O');
      if(result2) has_opponent= true;
          
    }
    if(has_us&&has_opponent)
    {
      return 0;// 公共区
    }
    else if(has_us)
    {
      return -4;
    }
    else 
      return 4;// 落到对手的领地

    // 一般不可能到这里的
    return 0;
  }
}

/**
 * 一个格子的分数
 * 子落到这个格子里得多少分
 */
export function score_of_step(board_state,move_pos_x,move_pos_y,chains, ns) 
{
  var scoreResult = 0;
  // 被包围情况:
  var score_surrounded = surrounded(board_state,move_pos_x,move_pos_y,ns);
  if(-3==score_surrounded)score_surrounded=-4;
  scoreResult+=score_surrounded;
  // 去包围对手的棋子:
  scoreResult+=surrounded_opponent(board_state,move_pos_x,move_pos_y,ns);
  // 形成链路:
  var score_for_chain = score_make_chain(board_state,move_pos_x,move_pos_y, ns)
  // ns.tprint("\t", move_pos_x,",",move_pos_y,"\t链路分:",score_for_chain);
  scoreResult+=score_for_chain;
  // 是不是落到了已生成的链中:
  var score_in_chain =score_inspace_surrounded(board_state,chains,move_pos_x,move_pos_y,ns);
  // ns.tprint("\t", move_pos_x,",",move_pos_y,"\t落到链路分:",score_in_chain);
  scoreResult+=score_in_chain;

  return scoreResult;
}

/**
 * {score:---,x:---,y:---}
 */
export function score_of_step_list(board_state,move_list,chains, ns) 
{
  var list_score =[];

  for(var i=0;i<move_list.length;++i)
  {
    var move_pos_x = move_list[i][0];
    var move_pos_y = move_list[i][1];
    var score_of_this_move = score_of_step(board_state,move_pos_x,move_pos_y,chains, ns);
    var obj_move_data = {score:score_of_this_move,x:move_pos_x,y:move_pos_y}
    list_score.push(obj_move_data);
  }

  //ns.tprint("算了多少步的分数:",list_score.length);

  // 对分数表进行排序
  for(var i=0;i<list_score.length-1;++i)
  {
    for(var j=0;j<list_score.length-1;++j)
    {
      if(list_score[j].score < list_score[j+1].score)
      {
        var temp = list_score[j];
        list_score[j] = list_score[j+1];
        list_score[j+1] = temp;
      }
    }// END for
  }// END for
  

  return list_score;
}